package com.zhangxu.microservice.auth.biz.service.impl;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.zhangxu.microservice.auth.biz.dto.CreateSystemDTO;
import com.zhangxu.microservice.auth.biz.dto.SystemDTO;
import com.zhangxu.microservice.auth.biz.dto.UpdateSystemDTO;
import com.zhangxu.microservice.auth.biz.mapstruct.SystemConverter;
import com.zhangxu.microservice.auth.biz.service.SystemService;
import com.zhangxu.microservice.auth.common.enums.SystemStatusEnum;
import com.zhangxu.microservice.auth.dao.condition.SystemCondition;
import com.zhangxu.microservice.auth.dao.entity.SystemDO;
import com.zhangxu.microservice.auth.dao.service.SystemDao;
import com.zhangxu.microservice.common.context.EmployeeContextHolder;
import com.zhangxu.microservice.common.exception.BizException;
import com.zhangxu.microservice.common.utils.AssertUtils;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

/**
 * 系统管理服务实现类
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class SystemServiceImpl implements SystemService {

    private final SystemDao systemDao;
    private final SystemConverter systemConverter;

    @Override
    public Long createSystem(CreateSystemDTO createSystemDTO) {
        // 检查系统编码是否已存在
        SystemDO existingSystem = systemDao.getBySystemCode(createSystemDTO.getSystemCode());
        if (existingSystem != null) {
            throw new BizException("系统编码已存在");
        }

        // 转换并保存系统
        SystemDO systemDO = systemConverter.toSystemDO(createSystemDTO);
        systemDO.setDeleteTime(0L);
        systemDO.setStatus(SystemStatusEnum.NEW);
        systemDao.save(systemDO);
        return systemDO.getId();
    }

    @Override
    public void updateSystem(UpdateSystemDTO updateSystemDTO) {
        // 检查系统是否存在
        SystemDO existingSystem = systemDao.getById(updateSystemDTO.getId());
        AssertUtils.notNull(existingSystem, "系统不存在");
        AssertUtils.isTrue(SystemStatusEnum.NEW.equals(existingSystem.getStatus()), "当前状态不能编辑");

        // 如果修改了系统编码，需要检查新编码是否已存在
        if (!existingSystem.getSystemCode().equals(updateSystemDTO.getSystemCode())) {
            SystemDO systemWithNewCode = systemDao.getBySystemCode(updateSystemDTO.getSystemCode());
            if (systemWithNewCode != null) {
                throw new BizException("系统编码已存在");
            }
        }

        // 转换并更新系统
        SystemDO systemDO = systemConverter.toSystemDO(updateSystemDTO);
        systemDao.updateById(systemDO);
    }

    @Override
    public void deleteSystem(Long systemId) {
        // 检查系统是否存在
        SystemDO existingSystem = systemDao.getById(systemId);
        AssertUtils.notNull(existingSystem, "系统不存在");
        AssertUtils.isTrue(SystemStatusEnum.NEW.equals(existingSystem.getStatus()), "当前状态不能删除");
        
        // 逻辑删除系统
        SystemDO systemDO = new SystemDO();
        systemDO.setId(systemId);
        systemDO.setDeleteTime(System.currentTimeMillis());
        systemDao.updateById(systemDO);
    }

    @Override
    public void enableSystem(Long systemId) {
        // 检查系统是否存在
        SystemDO existingSystem = systemDao.getById(systemId);
        AssertUtils.notNull(existingSystem, "系统不存在");
        AssertUtils.isFalse(SystemStatusEnum.ENABLE.equals(existingSystem.getStatus()), "当前状态不能启用");

        // 启用系统
        SystemDO systemDO = new SystemDO();
        systemDO.setId(systemId);
        systemDO.setStatus(SystemStatusEnum.ENABLE);
        systemDao.updateById(systemDO);
    }

    @Override
    public void disableSystem(Long systemId) {
        // 检查系统是否存在
        SystemDO existingSystem = systemDao.getById(systemId);
        AssertUtils.notNull(existingSystem, "系统不存在");
        AssertUtils.isTrue(SystemStatusEnum.ENABLE.equals(existingSystem.getStatus()), "当前状态不能禁用");

        // 禁用系统
        SystemDO systemDO = new SystemDO();
        systemDO.setId(systemId);
        systemDO.setStatus(SystemStatusEnum.DISABLE);
        systemDao.updateById(systemDO);
    }

    @Override
    public SystemDTO getSystemById(Long systemId) {
        SystemDO systemDO = systemDao.getById(systemId);
        return systemDO != null ? systemConverter.toSystemDTO(systemDO) : null;
    }

    @Override
    public SystemDTO getSystemByCode(String systemCode) {
        SystemDO systemDO = systemDao.getBySystemCode(systemCode);
        return systemDO != null ? systemConverter.toSystemDTO(systemDO) : null;
    }

    @Override
    public IPage<SystemDTO> systemPage(SystemCondition condition) {
        IPage<SystemDO> page = systemDao.page(condition);
        return page.convert(systemConverter::toSystemDTO);
    }
}